﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Net.WebSockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Web;
using System.Web.Script.Serialization;
using System.Web.WebSockets;
using MediaServer.Controllers;

namespace MediaServer.ClientHandler
{
    public class Client
    {
        #region Static Attributes
        static ObservableCollection<Client> Clients = new ObservableCollection<Client>();
        public static JavaScriptSerializer Serializer = new JavaScriptSerializer();
        #endregion

        #region Attributes
        AspNetWebSocket socket = null;
        #endregion

        #region Properties
        //User User { get; set; }
        #endregion

        public Client()
        {
            Client.Clients.Add(this);
        }

        #region Callbacks
        public async Task HoldConnection(AspNetWebSocketContext context)
        {
            socket = context.WebSocket as AspNetWebSocket;

            var inputBuffer = new ArraySegment<byte>(new byte[1024]);
            Info i = new Info() { Message = "Websocketconnection successfully established." };
            await this.SendMessage(i);
            try
            {
                while (true)
                {
                    var result = await socket.ReceiveAsync(inputBuffer, CancellationToken.None);
                    if (socket.State != WebSocketState.Open)
                    {
                        //Disconnected
                        break;
                    }
                    string msg = Encoding.UTF8.GetString(inputBuffer.Array, 0, result.Count);
                    this.ProcessMessage(msg);
                    //Handle message!
                    //var positionMessage = JsonConvert.DeserializeObject<PlayerPositionMessage>(messageString);
                    //YPos = positionMessage.YPos;
                    //if (PlayerMoved != null)
                    //    PlayerMoved(this, positionMessage);
                }
            }
            catch (Exception ex)
            {
                Debug.WriteLine(ex.Message);
                //Disconnected
            }
        }
        #endregion

        #region Methods
        async void ProcessMessage(string msg)
        {
            var requestMessage = Serializer.Deserialize<BaseRequest>(msg);
            switch (requestMessage.Type)
            {
                case "Album":
                    //AlbumController ac = new AlbumController();
                    AlbumRequest ar = (Serializer.Deserialize<AlbumRequest>(msg));
                    switch (ar.Action)
                    {
                        case "Next":
                            //var c = ac.Next(ar.ID);
                            //await SendMessage(new Data() { Content = c });
                            break;
                        case "Get":
                            break;
                    }
                    //SendMessage(new Data() { Content = ac.Get((requestMessage as AlbumRequest).ID) });
                    break;
                case "Video":
                    int i = 100;
                    while(i < 590)
                    {
                        //string url = @"C:\0work\CardGame\CardGame\Testbilder\test.jpg." + i + ".jpg";
                        string url = @"C:\0work\CardGame\CardGame\Hdbilder\The.Art.of.Flight.2011.1080p.Bluray.x264-MOMENTUM_000" + i + ".jpg";
                        Image image = null;
                        image = Image.FromFile(url);
                        //Bitmap bmp = new Bitmap(image);
                        //bmp.SetResolution(704, 480);
                        ImageConverter ic = new ImageConverter();
                        byte[] buffer = (byte[])ic.ConvertTo(image, typeof(byte[]));
                        //ArraySegment<byte> buffer = (ArraySegment<byte>)ic.ConvertTo(image, typeof(ArraySegment<byte>));
                        //base64String = Convert.ToBase64String(
                        //    buffer,
                        //    Base64FormattingOptions.InsertLineBreaks);
                        //using (MemoryStream ms = new MemoryStream())
                        //{
                        //    // Convert Image to byte[]
                        //    image.Save(ms, image.RawFormat);
                        //    byte[] imageBytes = ms.ToArray();

                        //    // Convert byte[] to Base64 String
                        //    base64String = Convert.ToBase64String(imageBytes);
                        //}
                        Debug.WriteLine("Sending File " + i + " ...");
                        if (socket != null && socket.State == WebSocketState.Open)
                        {
                            //var outputBuffer = new ArraySegment<byte>(Encoding.UTF8.GetBytes(messageString));
                            await socket.SendAsync(new ArraySegment<byte>(buffer), WebSocketMessageType.Binary, true, CancellationToken.None);
                        }
                        //SendMessage(new VideoImage() { Content = base64String, Part = i });
                        i++;
                    }
                    break;
                case "Thumbnails":
                    int x = 0;
                    while (x < 10)
                    {
                        string url = @"C:\0work\CardGame\CardGame\Hdbilder\The.Art.of.Flight.2011.1080p.Bluray.x264-MOMENTUM_000" + (250 + x * 10) + ".jpg";
                        Image image = null;
                        image = Image.FromFile(url);
                        ImageConverter ic = new ImageConverter();
                        byte[] buffer = (byte[])ic.ConvertTo(image, typeof(byte[]));
                        string base64String = "";
                        base64String = Convert.ToBase64String(
                            buffer,
                            Base64FormattingOptions.InsertLineBreaks);
                        using (MemoryStream ms = new MemoryStream())
                        {
                            // Convert Image to byte[]
                            image.Save(ms, image.RawFormat);
                            byte[] imageBytes = ms.ToArray();

                            // Convert byte[] to Base64 String
                            base64String = Convert.ToBase64String(imageBytes);
                        }
                        Debug.WriteLine("Sending " + (250 + x * 10) + " ...");
                        await this.SendMessage(new Thumbnail() { Description = "Thumbnail" + (250 + x * 10), FileType = "image", Content = base64String });
                        x++;
                    }
                    break;
            }
        }

        public async Task SendMessage(object message)
        {
            // serialize and send
            var messageString = Serializer.Serialize(message);
            if (socket != null && socket.State == WebSocketState.Open)
            {
                var outputBuffer = new ArraySegment<byte>(Encoding.UTF8.GetBytes(messageString));
                await socket.SendAsync(outputBuffer, WebSocketMessageType.Text, true, CancellationToken.None);
            }
        }
        #endregion
    }
}